import json
import logging
from django.http import JsonResponse, StreamingHttpResponse
from django.views import View
from .utils.spark_ai import SparkAIHandler
from .utils.qwen_ai import QwenAIHandler
from .utils.speech_recognition import SpeechRecognitionHandler
import requests
from django.conf import settings
from openai import OpenAI

logger = logging.getLogger(__name__)

class SmartGuideView(View):
    def post(self, request):
        try:
            logger.info("收到诊断请求")
            logger.info(f"请求路径: {request.path}")
            logger.info(f"请求方法: {request.method}")
            logger.info(f"请求头: {request.headers}")
            
            # 从 JSON 请求中获取数据
            data = json.loads(request.body)
            symptoms = data.get('symptoms', '')
            messages = data.get('messages', [])
            
            # 添加中医专家角色设定
            system_message = {
                'role': 'system',
                'content': '''你是一位经验丰富的中医专家。请根据患者的症状提供专业的中医诊断建议。
诊断建议需要包含以下内容，并以表格形式呈现：

1. 初步诊断
- 可能的病症（中医辨证）
- 症状严重程度
- 病因分析

2. 就医建议
- 建议就诊科室
- 就医等级
- 就医紧急度

3. 中医调理建议
- 推荐中药方剂
- 针灸穴位
- 推拿按摩建议

4. 生活起居指导
- 饮食调养
- 作息建议
- 情志调节

请确保诊断符合中医理论，建议实用可行。'''
            }
            
            # 更新消息列表
            messages = [system_message] + messages[1:]
            
            logger.info(f"症状: {symptoms}")
            logger.info(f"消息: {messages}")
            
            # 使用星火AI处理请求
            spark_handler = SparkAIHandler(streaming=False)
            result = spark_handler.generate_response(messages)
            
            logger.info(f"生成结果: {result}")
            
            return JsonResponse({
                'success': True,
                'result': result
            })
        except Exception as e:
            logger.error(f"处理请求时出错: {str(e)}", exc_info=True)
            return JsonResponse({
                'success': False,
                'error': str(e)
            }, status=500)

class MultiModalDiagnosisView(View):
    def post(self, request):
        try:
            logger.info("收到多模态问诊请求")
            
            # 检查请求大小
            content_length = request.META.get('CONTENT_LENGTH')
            if content_length and int(content_length) > settings.DATA_UPLOAD_MAX_MEMORY_SIZE:
                return JsonResponse({
                    'success': False,
                    'error': f'文件大小超过限制（最大 {settings.DATA_UPLOAD_MAX_MEMORY_SIZE // (1024 * 1024)}MB）'
                }, status=413)
            
            try:
                data = json.loads(request.body)
            except json.JSONDecodeError as e:
                logger.error(f"JSON解析失败: {str(e)}")
                return JsonResponse({
                    'success': False,
                    'error': '无效的请求数据格式'
                }, status=400)
            
            logger.info("请求头信息:")
            logger.info(f"Content-Type: {request.headers.get('Content-Type')}")
            logger.info(f"Content-Length: {request.headers.get('Content-Length')}")
            
            messages = data.get('messages', [])
            history = data.get('history', [])
            
            # 验证消息格式
            if not isinstance(messages, list):
                return JsonResponse({
                    'success': False,
                    'error': '消息格式无效'
                }, status=400)
            
            # 检查媒体文件大小
            for message in messages:
                if isinstance(message.get('content'), list):
                    for content in message['content']:
                        if isinstance(content, dict):
                            # 检查视频
                            if 'video_url' in content:
                                video_data = content['video_url']['url'].split('base64,')[1]
                                video_size = len(video_data) * 3 / 4  # Base64解码后的大小
                                if video_size > 10 * 1024 * 1024:  # 10MB
                                    return JsonResponse({
                                        'success': False,
                                        'error': '视频文件大小超过限制（最大10MB）'
                                    }, status=413)
                            # 检查图片
                            elif 'image_url' in content:
                                image_data = content['image_url']['url'].split('base64,')[1]
                                image_size = len(image_data) * 3 / 4
                                if image_size > 5 * 1024 * 1024:  # 5MB
                                    return JsonResponse({
                                        'success': False,
                                        'error': '图片文件大小超过限制（最大5MB）'
                                    }, status=413)
            
            # 设置系统角色
            system_message = {
                'role': 'system',
                'content': [{'type': 'text', 'text': '''您是一个资深中医专家，具有丰富的中医理论知识和临床经验。
                职责：为用户提供中医健康咨询、草药推荐、针灸疗法建议、食疗指导以及整体养生方案。
                您要根据用户的具体症状、生活习惯和体质特点，制定个性化的健康方案。'''}]
            }
            
            # 处理消息格式
            formatted_messages = [system_message]
            
            # 添加历史消息
            if history:
                try:
                    formatted_messages.extend(history)
                except Exception as e:
                    logger.error(f"处理历史消息失败: {str(e)}")
                    return JsonResponse({
                        'success': False,
                        'error': '历史消息格式无效'
                    }, status=400)
            
            # 添加当前消息
            formatted_messages.extend(messages)
            
            # 记录格式化后的消息（排除大型二进制数据）
            safe_messages = self._get_safe_log_messages(formatted_messages)
            logger.info(f"格式化后的消息: {json.dumps(safe_messages, indent=2)}")
            
            try:
                client = OpenAI(
                    api_key=settings.QWEN_CONFIG['API_KEY'],
                    base_url=f"{settings.QWEN_CONFIG['API_BASE']}/compatible-mode/v1"
                )
                
                api_params = {
                    'model': 'qwen-omni-turbo',
                    'messages': formatted_messages,
                    'modalities': ['text'],
                    'stream': True,
                    'stream_options': {'include_usage': True}
                }
                
                # 记录请求参数（排除敏感数据）
                safe_params = api_params.copy()
                if 'messages' in safe_params:
                    safe_params['messages'] = self._get_safe_log_messages(safe_params['messages'])
                logger.info(f"API请求参数: {json.dumps(safe_params, indent=2)}")
                
                logger.info("发送请求到千问API")
                completion = client.chat.completions.create(**api_params)
                
                response = StreamingHttpResponse(
                    self._stream_response(completion),
                    content_type='text/event-stream'
                )
                
                # 设置响应头
                response['Cache-Control'] = 'no-cache'
                response['Connection'] = 'keep-alive'
                response['X-Accel-Buffering'] = 'no'
                response['Transfer-Encoding'] = 'chunked'
                
                return response
                
            except Exception as e:
                error_detail = str(e)
                error_message = '模型服务请求失败'
                status_code = 503
                
                if hasattr(e, 'response'):
                    try:
                        error_response = e.response.json()
                        if 'error' in error_response:
                            error = error_response['error']
                            if error.get('message', '').startswith('Exceeded limit'):
                                error_message = '文件大小超过限制（图片最大5MB，视频最大10MB）'
                                status_code = 413
                            else:
                                error_message = error.get('message', error_message)
                    except:
                        pass
                
                logger.error(f"{error_message}: {error_detail}", exc_info=True)
                return JsonResponse({
                    'success': False,
                    'error': error_message,
                    'detail': error_detail
                }, status=status_code)
            
        except Exception as e:
            logger.error(f"处理请求失败: {str(e)}", exc_info=True)
            return JsonResponse({
                'success': False,
                'error': str(e)
            }, status=500)

    def _get_safe_log_messages(self, messages):
        """获取安全的日志消息，移除大型二进制数据"""
        safe_messages = []
        for msg in messages:
            safe_msg = msg.copy()
            if isinstance(safe_msg.get('content'), list):
                safe_content = []
                for item in safe_msg['content']:
                    if isinstance(item, dict):
                        safe_item = item.copy()
                        if 'image_url' in safe_item:
                            safe_item['image_url'] = {'url': '(image data)'}
                        elif 'video_url' in safe_item:
                            safe_item['video_url'] = {'url': '(video data)'}
                        safe_content.append(safe_item)
                    else:
                        safe_content.append(item)
                safe_msg['content'] = safe_content
            safe_messages.append(safe_msg)
        return safe_messages

    def _stream_response(self, completion):
        """处理流式响应"""
        def generate():
            try:
                logger.info("开始处理流式响应")
                for chunk in completion:
                    if hasattr(chunk, 'choices') and chunk.choices:
                        delta = chunk.choices[0].delta
                        if hasattr(delta, 'content') and delta.content:
                            response_data = {'content': delta.content}
                            yield f'data: {json.dumps(response_data)}\n\n'
                            logger.debug(f"发送内容: {delta.content}")
                    elif hasattr(chunk, 'usage') and chunk.usage:
                        if any(value > 0 for value in chunk.usage.__dict__.values()):
                            logger.info(f"Usage info: {chunk.usage}")
                
                logger.info("响应完成")
                yield 'data: [DONE]\n\n'
                
            except Exception as e:
                logger.error(f"流式响应处理失败: {str(e)}", exc_info=True)
                error_message = {"error": str(e)}
                yield f'data: {json.dumps(error_message)}\n\n'
        
        return generate()

class CheckModelConnectionView(View):
    def get(self, request):
        try:
            logger.info("收到连接检查请求")
            logger.info(f"请求路径: {request.path}")
            logger.info(f"请求方法: {request.method}")
            logger.info(f"请求头: {request.headers}")
            
            # 创建 SparkAI 处理器实例并进行简单的生成测试
            spark_handler = SparkAIHandler(streaming=False)
            test_messages = [
                {
                    'role': 'system',
                    'content': [{'type': 'text', 'text': 'You are a helpful assistant.'}]
                },
                {
                    'role': 'user',
                    'content': [{'type': 'text', 'text': '你好'}]
                }
            ]
            result = spark_handler.generate_response(test_messages)
            
            logger.info("连接检查成功")
            return JsonResponse({
                'success': True,
                'message': '连接配置正确',
                'test_response': result
            })
        except Exception as e:
            logger.error(f"连接检查失败: {str(e)}", exc_info=True)
            return JsonResponse({
                'success': False,
                'message': str(e)
            }, status=500)

class SpeechRecognitionView(View):
    def post(self, request):
        try:
            logger.info("收到语音识别请求")
            
            # 检查请求大小
            content_length = request.META.get('CONTENT_LENGTH')
            if content_length and int(content_length) > 5 * 1024 * 1024:  # 5MB限制
                return JsonResponse({
                    'success': False,
                    'error': '音频文件大小超过限制（最大5MB）'
                }, status=413)
            
            # 获取音频数据
            audio_data = request.body
            
            # 处理语音识别
            handler = SpeechRecognitionHandler()
            result = handler.process_audio(audio_data)
            
            if result['success']:
                return JsonResponse({
                    'success': True,
                    'text': result['text']
                })
            else:
                return JsonResponse({
                    'success': False,
                    'error': result['error']
                }, status=500)
                
        except Exception as e:
            logger.error(f"处理语音识别请求失败: {str(e)}", exc_info=True)
            return JsonResponse({
                'success': False,
                'error': str(e)
            }, status=500) 